home *** CD-ROM | disk | FTP | other *** search
/ Gekkan Dennou Club 145 / Gekkan Dennou Club - 2000.6 Vol. 145 (Japan).7z / Gekkan Dennou Club - 2000.6 Vol. 145 (Japan) (Track 1).bin / games / spassion / source.lzh / SOURCE / OPEN_END.C < prev    next >
Text File  |  2000-03-31  |  14KB  |  564 lines

  1. /* オープニングとエンディング */
  2. #include <stdio.h>
  3. #include <string.h>
  4. #include <doslib.h>
  5. #include <iocslib.h>
  6. #include <math.h>
  7. #include <apic.h>
  8. #include <XSP2lib.H>
  9. #include "SPASSION.H"
  10. #include "PLAYER.H"
  11. #include "SHOT.H"
  12. #include "PRIORITY.H"
  13. #include "BG.H"
  14. #include "SOUND.H"
  15. #include "SUB.H"
  16. #define SP_X( x )    (*((short *)(&x)));    /*lxの上位ワード*/
  17. #define SP_Y( y )    (*((short *)(&y)));    /*lyの上位ワード*/
  18. #define PLAYER_DIR1            6
  19. #define PLAYER_DIR2            12
  20. #define APP_PT                12
  21.  
  22. void    ras_scroll() ;
  23. void    ras_scroll_init() ;
  24.  
  25. XSP_TIME_CHART    time_chart[512] ;    /* ユーザー側ラスター割り込みタイムチャート */
  26. static short    wave[ 256 ] ;        /* うねりデーター */
  27. static short    wave_ptr = 0 ;        /* うねりデーター読み出し位置のインデックス */
  28. static short    wave_ptr_00 = 0 ;    /* うねりデーター読み出し位置のインデックスの初期値 */
  29.  
  30. /* オープニングで使う文章用 */
  31. typedef struct SENTENCE{
  32.     char    *str;    /* 文章 */
  33.     short    info;    /* 1で中央寄せする */
  34. }SENTENCE;
  35.  
  36. /* 文字列を真ん中に揃えて表示 */
  37. void printf_( SENTENCE *sentence )
  38. {
  39.     short    lng,x,i;
  40.     char    str[255];
  41.  
  42.     if(sentence->info){
  43.         lng=strlen(sentence->str);
  44.         x=(32-lng/2)/2;
  45.         for(i=0;i<x;i++)
  46.             FPUTS(" ",2);        /*空白を作る*/
  47.         if( (32-lng/2)%2 )
  48.             FPUTC(' ',2);        /*空白を作る*/
  49.     }
  50.     sprintf(str,"%s",sentence->str);
  51.     FPUTS(str,2);
  52. }
  53. void Opening( void )
  54. {
  55.     short    ty=512,i=0,j,cur_y=0,cur_y2=1,count=0;
  56.     unsigned short    *p=(unsigned short *)0xE80016;
  57.     SENTENCE    opening_str[]={
  58. /*        "                                                                ",*/
  59.         "「Active Shoot」から数カ月、彼の就職活動は、",1,
  60.         "",0,
  61.         "",0,
  62.         "未だに収束の気配すら見せずにいた。",1,
  63.         "",0,
  64.         "",0,
  65.         "",0,
  66.         "",0,
  67.         "「おっ、××社からの郵便だ。なになに? 『残念ながらご希望に沿",0,
  68.         "",0,
  69.         " うことが出来ず・・・』 キーッ! あたしの作品のどこが気に入",0,
  70.         "",0,
  71.         " らないっていうの! くやしー!」",0,
  72.         "",0,
  73.         " 齢24を過ぎ、さすがの彼も焦っていた。",0,
  74.         "",0,
  75.         "",0,
  76.         "",0,
  77.         "",0,
  78.         " 彼は言う。",1,
  79.         "",0,
  80.         "就職、それは",1,
  81.         "",0,
  82.         "夢をかなえるための手段に過ぎないと。",1,
  83.         "",0,
  84.         "",0,
  85.         "「就職しないと御飯が食べられないし、彼女もできないし、",0,
  86.         "",0,
  87.         " ていうか零式が買えないじゃないか。」",0,
  88.         "",0,
  89.         "",0,
  90.         "彼は願う。",1,
  91.         "",0,
  92.         "自分の作ったゲームで、",1,
  93.         "",0,
  94.         "子供達が目を輝かせてくれることを。",1,
  95.         "",0,
  96.         "",0,
  97.         "「○○も、△△も、果ては××まで門前払いとは・・・。",0,
  98.         "",0,
  99.         " 面接ぐらいさせてくれたっていいじゃねーか・・・",0,
  100.         "",0,
  101.         " ぶつぶつ・・・。」",0,
  102.         "",0,
  103.         "",0,
  104.         "そして今、新たに完成した作品を引っ提げ、",1,
  105.         "",0,
  106.         "未来への一歩を踏み出す。",1,
  107.         "",0,
  108.         "",0,
  109.         "「俺を採用しなかったことを後悔させてやる!」",1,
  110.         "",0,
  111.         "",0,
  112.         "",0,
  113.         "",0,
  114.         " 途中、WinでDirectXなんぞに手を染めたりもしながら、",1,
  115.         "",0,
  116.         "しつこくX68kで作品を作り続けるのであった。",1,
  117.         "",-1
  118.     };
  119.     void    VdispRoutine( void );
  120.  
  121. /*-----[ ユーザー側ラスター割り込みタイムチャート作成 ]-----*/
  122.     i=0 ;
  123.     for ( j=0 ; j<512 ; j+=8 )
  124.     {
  125.         time_chart[i].ras_no    = j*2+32 ;
  126.         time_chart[i].proc        = ras_scroll ;
  127.         i++ ;
  128.     }
  129.  
  130.     time_chart[i].ras_no    = -1 ;        /* エンドマーク */
  131.  
  132.  
  133. /*--------[ ラスタースクロール用うねりデーター作成 ]--------*/
  134. /*    for ( i=0 ; i<512 ; i++ )*/
  135.     for ( i=0 ; i<256 ; i++ )
  136.     {
  137.         wave[i] = sin( 3.1415926535898 * (double)i/128 ) * 128 ;
  138.     }
  139.  
  140.     CRTMOD( 12 );            /* 512*512dot 655366色 グラフィックプレーン1枚 31kHz */
  141.     G_CLR_ON();
  142.     B_CONSOL(0, 0, 127, 63);
  143.     CONTRAST(0);
  144.     VPAGE(0);                /* 表示を消す */
  145.     APAGE(0);apic_load("PIC/OPENING.PIC",0,0);
  146.     xsp_vsyncint_on( ras_scroll_init ) ;    /* 帰線期間割り込み開始 */
  147.     xsp_hsyncint_on( time_chart ) ;            /* ラスター割り込み開始 */
  148.     VPAGE(1);                /* 表示 */
  149.  
  150.     xsp_vsync( 30 );            /* 時間稼ぎ */
  151.     PlayBGM( MUSIC_OPENING );        /* 音楽 */
  152.     while( CONTRAST(-1) != 15 ){
  153.         CONTRAST(++i);
  154.         xsp_vsync( 8 );
  155.     }
  156.     xsp_vsync( 60 );            /* 時間稼ぎ */
  157.  
  158.     i=0;
  159.     *p=ty;        /* スクロール値設定 */
  160.     while( !(GetKeyM( 0 ) & 0xF0) ){        /* ジョイスティックのボタンが押されたら出る */
  161.         if( !(ty%16) ){
  162.             if( opening_str[i].info != -1 ){
  163.                 B_LOCATE(0,cur_y);
  164.                 printf_(&opening_str[i++]);
  165.                 B_LOCATE(0,cur_y2);
  166.                 B_ERA_AL();                    /* クリア */
  167.                 cur_y++;
  168.                 cur_y&=63;
  169.                 cur_y2=cur_y+1;
  170.                 cur_y2&=63;
  171.             }else{
  172.                 B_LOCATE(0,cur_y2);
  173.                 B_ERA_AL();                    /* クリア */
  174.                 cur_y2++;
  175.                 cur_y2&=63;
  176.                 count++;
  177.             }
  178.         }
  179.  
  180.         xsp_vsync( 3 );
  181.         ty++;                        /* スクロール値を増やす */
  182.         ty&=1023;
  183.         *p=ty;
  184.         if( count > 32 )break;        /* 最終行がスクロールし終えた */
  185.     }
  186.  
  187.     FadeOut( 96 );
  188.     for(i=15;i>0;i--){
  189.         CONTRAST(i);
  190.         xsp_vsync( 2 );
  191.     }
  192.     xsp_vsync( 60 );
  193.     xsp_vsyncint_off();
  194.     xsp_hsyncint_off();
  195. }
  196. /*
  197.     帰線期間割り込みサブルーチン
  198. */
  199. void    ras_scroll_init()
  200. {
  201.     wave_ptr    = wave_ptr_00 ;
  202. /*    wave_ptr_00    =(wave_ptr_00 + 1) & 511 ;*/
  203.     wave_ptr_00    =(wave_ptr_00 + 1) & 255 ;
  204. }
  205.  
  206.  
  207. /*
  208.     ラスター割り込みサブルーチン
  209. */
  210. void    ras_scroll()
  211. {
  212.     *(short *)(0xE80018) = wave[ wave_ptr ] ;    /* グラフィックプレーン0 X座標 */
  213. /*    wave_ptr = (wave_ptr + 1) & 511 ;*/
  214.     wave_ptr = (wave_ptr + 1) & 255 ;
  215. }
  216.  
  217. /* エンディングで使う文字列用 */
  218. typedef struct STR{
  219.     short    x,y;        /* 座標 */
  220.     char    *str;        /* 文字列 */
  221. }STR;
  222.  
  223. void MoveStr( STR *str, short i )
  224. {
  225.     short    lng,gx,y;
  226.     lng     =strlen(str->str);
  227.     gx     =(16-lng)*10/2*16/10;    /* 小数対応のため10倍している。実際は (16-lng)/2*16 */
  228.     y     =str->y;
  229.     if( i%2 ){
  230.         if( (str->x+=2) > gx )
  231.             str->x=gx;
  232.     }else{
  233.         if( (str->x-=2) < gx )
  234.             str->x=gx;
  235.     }
  236.     PutBGStr( str->x, y, str->str, INFO_MOJI);
  237. }
  238.  
  239. void ChangeStage( short stage )
  240. {
  241.     unsigned short *pal=(unsigned short *)0xE82220;
  242.     short    i;
  243.     char    *stage_pic[STAGES*2]={
  244.         "PIC/STAGE1_0.PIC","PIC/STAGE1_1.PIC",
  245.         "PIC/STAGE2.PIC",  "PIC/STAGE2.PIC",
  246.         "PIC/STAGE3_0.PIC","PIC/STAGE3_1.PIC",
  247.         "PIC/STAGE4_0.PIC","PIC/STAGE4_1.PIC",
  248.     };
  249.  
  250.     BGCTRLST(1, 1, 0);            /* BG1表示OFF */
  251.     VPAGE(0);                    /* 表示を消す */
  252.     HOME( 0, 0 ,0 );
  253.     HOME( 1, 0 ,0 );
  254.     APAGE(1);apic_load(stage_pic[stage*2]  ,0,0);
  255.     APAGE(0);apic_load(stage_pic[stage*2+1],0,0);
  256.     VPAGE(3);                /* 表示 */
  257.  
  258.     for(i=0;i<16;i++)
  259.         *(pal++)=bg_pal[stage][i];
  260.     for(i=0;i<256;i++)
  261.         SP_DEFCG(i, 0, &bg_sp[stage][i*32]);
  262.     SetBG(32*3,0);
  263.     BGCTRLST(1, 1, 1);            /* BG1表示ON */
  264.  
  265.      gr1_x=0; gr1_y=0; gr1_vx=-32768;gr1_vy=0;
  266.      gr2_x=0; gr2_y=0; gr2_vx=-21845;gr2_vy=0;
  267.     map_x=(32*3*8)<<16;map_y=0;map_vx=-DOT_RATE/4;map_vy=0;
  268.     player[0].lx     = (256+32+16)<<16;
  269.     player[0].ly     = (128+16)<<16;
  270.     player[0].vx     = -65536/2;
  271.     player[0].state     = 0;
  272.     player[1].lx     = (256+32+16)<<16;
  273.     player[1].ly     = (128+16)<<16;
  274.     player[1].vx     = -65536/2;
  275.     player[1].state     = 0;
  276. }
  277.  
  278. /* ステージを戻る */
  279. void Ending( void )
  280. {
  281.     short    st=0,end,end_timer=0,str_state,player_flag;
  282.     char    button=0,break_flag=0;
  283.     short    count=0,i=0,con,con_count;
  284.     void    ChangeZPD( short num );
  285.     short    MovePlayerEnding( PLAYER *player );
  286.     void    Disp( void );
  287.  
  288.     STR        ending_str[STAGES][16]={
  289.     {
  290.         { 0, 5*16,"Special"},
  291.         { 0, 6*16,"Thanks"},
  292.         { 0, 8*16,"F.Yosshin"},
  293.         { 0, 9*16,"&XSP System"},
  294.         { 0, 0,"_"},
  295.  
  296.         { 0, 5*16,"Thank You"},
  297.         { 0, 7*16,"For"},
  298.         { 0, 9*16,"Playing!"},
  299.         { 0, 0,NULL},
  300.     },
  301.     {
  302.         { 0, 5*16,"OpeningGraphic"},
  303.         { 0, 7*16,"Shinnichi Sato"},
  304.  
  305.         { 0, 9*16,"Program"},
  306.         { 0,11*16,"Koji Sato"},
  307.         { 0, 0,NULL},
  308.     },
  309.     {
  310.         { 0, 3*16,"Music"},
  311.         { 0, 5*16,"Mark44."},
  312.         { 0, 6*16,"H.Mizuno"},
  313.  
  314.         { 0, 8*16,"SoundEffect"},
  315.         { 0,10*16,"H.Suzuki"},
  316.         { 0,11*16,"K.Matsumoto"},
  317.         { 0,12*16,"Quoz"},
  318.         { 0,13*16,"SJOM"},
  319.         { 0,14*16,"&Others"},
  320.         { 0, 0,NULL},
  321.     },
  322.     {
  323.         { 0, 4*16,"Sprite"},
  324.         { 0, 6*16,"MSY."},
  325.         { 0, 7*16,"M.N.B.S"},
  326.         { 0, 9*16,"BG&Font"},
  327.         { 0,11*16,"MSY."},
  328.         { 0, 0,NULL},
  329.     }
  330.     };
  331.  
  332.     player[0].pt     = obj_player+2;
  333.     player[0].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  334.     player[0].option[0].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  335.     player[0].option[1].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  336.     if( play_mode == MODE_2P ){
  337.         player[1].pt     = obj_player+2;
  338.         player[1].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  339.         player[1].option[0].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  340.         player[1].option[1].info     = 0x4000|PALET_PLAYER|PRIORITY_PLAYER;
  341.     }
  342.  
  343. /*    ChangeZPD( 1 );*/        /*エンディング用のZPDファイル*/
  344.     xsp_vsync( 90 );
  345.     PlayBGM( MUSIC_ENDING );
  346.  
  347. /* スタッフロール */
  348.     for(;stage>=0;stage--){
  349.         ChangeStage( stage );
  350.         for(i=0;ending_str[stage][i].str;i++){        /* 文字列表示 */
  351.             short    lng,gx;
  352.             lng     =strlen(ending_str[stage][i].str);
  353.             gx     =(16-lng)*10/2*16/10;    /* 小数対応のため10倍している。実際は (16-lng)/2*16 */
  354.             if( i%2 )
  355.                 ending_str[stage][i].x=gx-256;
  356.             else
  357.                 ending_str[stage][i].x=gx+256;
  358.         }
  359.         str_state=0;player_flag=0;end=1;con=0;con_count=0;
  360.         while( 1 ){
  361.             switch (str_state){
  362.             case 0:            /* 文字列入場 */
  363.                 for(i=st;i<end;i++)        /* 文字列表示 */
  364.                     MoveStr( &ending_str[stage][i], i );
  365.                 if( ++end_timer>60 ){    /* 最後の文字列が出てから1秒たった */
  366.                     end++;
  367.                     end_timer=0;
  368.                     if(!ending_str[stage][end].str || ending_str[stage][end].str[0]=='_')
  369.                         str_state++;
  370.                 }
  371.                 break;
  372.             case 1:            /* 入場し終えるのを待つ */
  373.                 for(i=st;i<end;i++)        /* 文字列表示 */
  374.                     MoveStr( &ending_str[stage][i], i );
  375.                 if( ++end_timer>60*4 ){    /* 最後の文字列が出てから4秒たった */
  376.                     end_timer=0;
  377.                     end=st+1;
  378.                     str_state++;
  379.                 }
  380.                 break;
  381.             case 2:            /* 文字列退場 */
  382.                 for(i=st;i<end;i++){
  383.                     if( i%2 )
  384.                         ending_str[stage][i].x+=2;
  385.                     else
  386.                         ending_str[stage][i].x-=2;
  387.                 }
  388.                 for(i=st;
  389.                     ending_str[stage][i].str && ending_str[stage][i].str[0]!='_';
  390.                     i++)            /* 文字列表示 */
  391. /*                for(i=st;i<end;i++)*/            /* 文字列表示 */
  392.                     PutBGStr( ending_str[stage][i].x, ending_str[stage][i].y, ending_str[stage][i].str, INFO_MOJI);
  393.  
  394.                 if( ++end_timer>30 ){    /* 最後の文字列が出てから0.5秒たった */
  395.                     end++;
  396.                     end_timer=0;
  397.                     if(!ending_str[stage][end].str || ending_str[stage][end].str[0]=='_')
  398.                         str_state++;
  399.                 }
  400.                 break;
  401.             case 3:            /* 退場し終えるのを待つ */
  402.                 for(i=st;i<end;i++){
  403.                     if( i%2 )
  404.                         ending_str[stage][i].x+=2;
  405.                     else
  406.                         ending_str[stage][i].x-=2;
  407.                 }
  408.                 for(i=st;i<end;i++)        /* 文字列表示 */
  409.                     PutBGStr( ending_str[stage][i].x, ending_str[stage][i].y, ending_str[stage][i].str, INFO_MOJI);
  410.                 if( ++end_timer>60*2 ){    /* 最後の文字列が出てから2秒たった */
  411.                     end_timer=0;
  412.                     if( !ending_str[stage][end].str ){
  413.                         st=0;
  414.                         str_state++;
  415.                     }else{
  416.                         st=end+1;
  417.                         str_state=0;
  418.                     }
  419.                     end=st+1;
  420.                 }
  421.                 break;
  422.             }
  423.  
  424.             if( !MovePlayerEnding( &player[0] ))    /* 1P自機移動 */
  425.                 player_flag=1;
  426.             if( play_mode == MODE_2P )
  427.                 MovePlayerEnding( &player[0] );        /* 2P自機移動 */
  428.  
  429.             if( player_flag && str_state > 3 ){
  430.                 con=(con_count--)/4;
  431.                 CONTRAST(con);
  432.                 if( !CONTRAST(-1) )
  433.                     break;
  434.             }else{
  435. /*                if( con!=15 ){
  436.                     con=(con_count++)/4;
  437.                     CONTRAST(con);
  438.                 }else{
  439.                     con=15;con_count=15*4;
  440.                 }
  441. */
  442.                 if( con!=15 ){
  443.                     con++;
  444.                     CONTRAST(con);
  445.                 }else{
  446.                     con=15;con_count=15*4;
  447.                 }
  448.             }
  449.  
  450.             bg_x=(map_x>>16)&0x1FF;
  451.             bg_y=(map_y>>16)&0x1FF;
  452.             ScrollBG();                        /* BGスクロール */
  453.             map_x+=map_vx;
  454.             gr1_x+=gr1_vx;gr1_y+=gr1_vy;    /* 背景スクロール */
  455.             gr2_x+=gr2_vx;gr2_y+=gr2_vy;
  456.             Disp();
  457.  
  458.             if( count++ > 60*3 ){
  459.                 count=60*3;
  460.                 button=GetKeyM( player[0].num )&0xF0;
  461.                 if( button ){        /* キーが押されたら出る */
  462.                     break_flag=1;
  463.                     break;
  464.                 }
  465.             }
  466.         }
  467.         if(break_flag)break;
  468.     }
  469.  
  470.     FadeOut( 96 );
  471.     con=15;
  472.     while( CONTRAST(-1) != 0 ){
  473.         xsp_vsync( 4 );
  474.         CONTRAST(--con);
  475.     }
  476.     CONTRAST(15);
  477. }
  478.  
  479. /* 画面右から中央へ、上を回って左へ */
  480. short MovePlayerEnding( PLAYER *player )
  481. {
  482.     unsigned char    pt_dir,i;
  483.  
  484.     /* 移動量を足す */
  485.     player->lx+=player->vx;
  486.     player->ly+=player->vy;
  487.     player->x = (*((short *)(&player->lx)));    /*lxの上位ワード*/
  488.     player->y = (*((short *)(&player->ly)));    /*lyの上位ワード*/
  489.  
  490.     if( player->vy < 0 ){
  491.         if( player->dir > -PLAYER_DIR2-6 )player->dir--;
  492.     }else if( player->vy > 0 ){
  493.         if( player->dir <  PLAYER_DIR2+6 )player->dir++;
  494.     }else{
  495.         if( player->dir > 0 )player->dir--;
  496.         else player->dir++;
  497.     }
  498.  
  499.     if( player->dir > PLAYER_DIR2 )      pt_dir=4;
  500.     else if( player->dir >  PLAYER_DIR1 )pt_dir=3;
  501.     else if( player->dir > -PLAYER_DIR1 )pt_dir=2;
  502.     else if( player->dir > -PLAYER_DIR2 )pt_dir=1;
  503.     else pt_dir=0;
  504.  
  505.     player->pt=obj_player+pt_dir;
  506.  
  507.     switch( player->state ){
  508.     case 0:                            /* 右から中央 */
  509.         if( player->x < 128+16 ){
  510.             player->vy = -65536/4;
  511.             player->state++;
  512.         }
  513.         break;
  514.     case 1:                            /* ちょっと後退 */
  515.         player->vx += 256;
  516.         if( player->vx > 0 ){
  517.             if( player->vx > 65536/4 ){
  518.                 player->state++;
  519.                 player->vy = 0;
  520.             }
  521.         }
  522.         break;
  523.     case 2:                            /* 左へ */
  524.         player->vx -= 1024;
  525.         if( player->x < -32+16 )
  526.             return 0;
  527.         if( PLAYER_X < 32+16 )
  528.             player->pt=obj_player+APP_PT+3;
  529.         else if( PLAYER_X < 64+16 )
  530.             player->pt=obj_player+APP_PT+2;
  531.         else if( PLAYER_X < 96+16 )
  532.             player->pt=obj_player+APP_PT+1;
  533.         else if( PLAYER_X < 128+16 )
  534.             player->pt=obj_player+APP_PT+0;
  535.         break;
  536.     }
  537.  
  538.  
  539.     /* オプション */
  540.     if( player->option_anim_count==0 )
  541.         player->option_anim_count=4;
  542.     else
  543.         player->option_anim_count=0;
  544.  
  545.     player->option[0].lx=player->old_lx[(player->pointer-4) & 255];
  546.     player->option[0].ly=player->old_ly[(player->pointer-4) & 255]-24*DOT_RATE;
  547.     player->option[1].lx=player->old_lx[(player->pointer-4) & 255];
  548.     player->option[1].ly=player->old_ly[(player->pointer-4) & 255]+24*DOT_RATE;
  549.  
  550.     for(i=0;i<2;i++){
  551.         player->option[i].pt=obj_option+pt_dir/2+player->option_anim_count;
  552.         player->option[i].x = (*((short *)(&player->option[i].lx)))-8;    /*lxの上位ワード*//*-8は表示位置をずらすため*/
  553.         player->option[i].y = (*((short *)(&player->option[i].ly)))-8;    /*lyの上位ワード*/
  554.         xsp_set_st( &player->option[i] );
  555.     }
  556.     player->old_lx[player->pointer]=player->lx;
  557.     player->old_ly[player->pointer]=player->ly;
  558.     player->pointer++;
  559.     player->pointer&=255;
  560.  
  561.     xobj_set_st( player );
  562.     return 1;
  563. }
  564.